package com.cefa.edu.service;

import com.cefa.edu.dao.*;
import com.cefa.edu.model.CefaEduSample;
import com.cefa.edu.model.EducationLevel;
import com.cefa.edu.model.Graduation;
import com.cefa.edu.model.User;
import com.cefa.edu.pojo.Grade;
import com.cefa.edu.pojo.OrganRelation;
import com.cefa.edu.pojo.Phase;
import com.cefa.edu.pojo.StudentStageData;
import com.cefa.edu.util.TimeUtil;
import org.apache.commons.collections.map.HashedMap;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;

/**
 * @author huangzehui
 * @date 18-8-2 上午9:02
 */

@Service
public class ScheduledService {

    @Autowired
    ScheduledMapper scheduledMapper;

    @Autowired
    EducationLevelMapper educationLevelMapper;

    @Autowired
    UserMapper userMapper;
    @Autowired
    UserRoleMapper userRoleMapper;
    @Autowired
    CourseMapper courseMapper;
    @Autowired
    ClassMapper classMapper;
    @Autowired
    PhaseMapper phaseMapper;
    @Autowired
    GradeMapper gradeMapper;
    @Autowired
    OrganRelationMapper organRelationMapper;
    @Autowired
    UserOrganRoleMapper userOrganRoleMapper;
    @Autowired
    EduStageMapper eduStageMapper;

    /**
     * 学生流转
     * @return
     */
    @Transactional("transactionManager")
    public void  studentCirculation() {
        //1、比如高中，第一步先把高三的班级数据与年级数据 断掉，把年级数据关联到另外一张新建的表中，并且p_id 和g_id 设置成空
        //2、第二步，把高二的班级数据和之前的年级数据关系断掉，把班级数据关联到高三上,
        //3、同第二步一样高一升到高二
        //4、那么高一的所有班级就没了，现在程序自动生成原来的班级，并且级+1,但是没有老师和学生只有班级，如果有初中升高中时，需要重新在高一年级下添加学生和老师

        //如果是多个学校，只需查询admin用户即可
        List<User> userList= userRoleMapper.getUserRoleByType(1);//一个学校只有一个admin角色用户,考虑到多个学校的情况
        for (User user:userList){
            List<EducationLevel> educationLevelList=educationLevelMapper.getEducationLevel(user.getId(),1);//1层
            //是一层管理者
            Map<Integer,EducationLevel> map= new HashMap<Integer,EducationLevel>();
            for(EducationLevel el :educationLevelList){
                List<EducationLevel> list=  educationLevelMapper.getEducationLevelByPid(el.getId());//二级 高一、高二、高三，或者时初一、初二、初三,sql已经排好序了
                //获取当前年份数据 比如2019年
                //int correntYear=2019;
                int correntYear = Calendar.getInstance().get(Calendar.YEAR);
                if(el.getSort()==6){//小学6年制
                    for (EducationLevel educationLevel:list){
                        //sql有排序 从低到高
                        List<EducationLevel> list2= educationLevelMapper.getEducationLevelByPid(educationLevel.getId());
                        for (EducationLevel dl:list2){
                            int count=correntYear-Integer.parseInt(dl.getGradeDate());
                            if(count==1){//小学一年级升二年级
                                headTeacher( dl, list, count);
                            }else if(count==6){//六年级毕业
                                centerTeacher( dl, list, count);
                            }else{//二年级升三年级，三年级升四年级，四年级升五年级，五年级升六年级
                                endTeacher( dl, educationLevel, el);
                            }
                        }
                    }
                }else if(el.getSort()==3){//初中、高中三年制；假设时高中
                    for (EducationLevel educationLevel:list){//是根据高一、高二、高三排序
                        //sql有排序 ，肯定第一个时高一或者初一，之后时高二或者初二、最后时高三或者初三
                        List<EducationLevel> list2= educationLevelMapper.getEducationLevelByPid(educationLevel.getId());//查询二级下的所有班级，可能时高一下的所有班级，也可能是高三下的所有班级，根据级判断是高几或者初几
                        //如果是高一（如果时初一）
                        for (EducationLevel dl:list2){
                            int count=correntYear-Integer.parseInt(dl.getGradeDate());
                            if(count==1){//高一升高二
                                headTeacher( dl, list, count);
                            }else if(count==2){//高二升高三
                                centerTeacher( dl, list, count);
                            }else if(count==3){//高三毕业班级
                                endTeacher( dl, educationLevel, el);
                            }
                        }
                    }
                }else if(el.getSort()==4){//幼儿园 四年制
                    for (EducationLevel educationLevel:list){
                        //sql有排序 从低到高
                        List<EducationLevel> list2= educationLevelMapper.getEducationLevelByPid(educationLevel.getId());
                        for (EducationLevel dl:list2){
                            int count=correntYear-Integer.parseInt(dl.getGradeDate());
                            if(count==1){//学前班升小班
                                headTeacher( dl, list, count);
                            }else if(count==4){//幼儿园毕业
                                centerTeacher( dl, list, count);
                            }else{//小班升中班、中班升大班
                                endTeacher( dl, educationLevel, el);
                            }
                        }
                    }
                }
            }
            //所有年级都+1
            educationLevelMapper.updateLevelByschoolId(user.getSchoolId());
        }
    }

    /**
     * 这些是老师不跟者班级走的逻辑 1升级2的逻辑
     * @param dl
     * @param list
     * @param count
     */
    public void head(EducationLevel dl,List<EducationLevel> list,int count){

        //1、把该层级（班级）下的pid改成高二对应的id，2、把老师、班主任和该班级的关联断掉？？？？？？？？？？？？？
        //相当于高一里的年级都没了（因为原来的高一要升级到高二），程序自动创建并且把现在升级高二的对应的老师关联到新生层的高一班级，那么现在由高一升级到高二的年级现阶段就没有老师了



        //2 因为没有老师了，需要查询原来的高二,某班级名称 查询，如果有，那么把高二下的老师都关联到新升级的高二班，
        //如果没查到，就默认新升级到高二的这个班级没有老师
        List<EducationLevel> elist=educationLevelMapper.getEducationLevelBypIdAndName(list.get(count).getId(),dl.getName());
        //创建一个班级，就是插入一条第三层层级，
        Integer levelId=dl.getId();
        dl.setGradeDate(dl.getGradeDate()+1);
        educationLevelMapper.insertEducationLevel(dl);
        dl.setId(null);
        userMapper.updateInstructorByLevelId(dl.getId(),levelId);

        educationLevelMapper.updateLevelPid(dl.getId(),list.get(count).getId());//原来时高一，现在是高二的班级现在已经没有老师关联了

        if(elist!=null&&elist.size()>0){//如果为空，意思就是高一比如是四班，在原来的高二里没有四班这个班，那么高一升级上来就默认没有老师
            userMapper.updateInstructorByLevelId(levelId,elist.get(0).getId());//把原来老的高二班级所对应的老师关联到新生级上来的高二,那么原来的高二的那个班级已经没有老师了
        }
    }


    /**
     * 这些是老师不跟者班级走的逻辑 未毕业的逻辑
     * @param dl
     * @param list
     * @param count
     */
    public void center(EducationLevel dl,List<EducationLevel> list,int count){
        educationLevelMapper.updateLevelPid(dl.getId(),list.get(count).getId());//把原来是
        List<EducationLevel> elist=educationLevelMapper.getEducationLevelBypIdAndName(list.get(count).getId(),dl.getName());
        if(elist!=null&&elist.size()>0){//如果为空，意思就是高二比如是四班，在原来的高三里没有四班这个班，那么高二升级上来就默认没有老师
            userMapper.updateInstructorByLevelId(dl.getId(),elist.get(0).getId());
        }
        //不管本来是高二的班级还有没有和老师的关联数据，都要清除掉(如果count=1的时候list查到了，那么就没有了关联，如果在count=1时list没查到，那么就还是有关联，需要删掉，因为高二升级到高三时原来的教高二的老师已经不能教高三了)
        educationLevelMapper.deleteUserEducationLevelByLevelId(dl.getId());
    }

    /**
     * 这些是老师不跟者班级走的逻辑 毕业的逻辑
     * @param dl
     * @param list
     * @param count
     * @param educationLevel
     * @param el
     */
    public void end(EducationLevel dl,List<EducationLevel> list,int count,EducationLevel educationLevel,EducationLevel el){
        //新表创建一条高三毕业数据和该高三或初三毕业班建立链接，并且把该高三毕业班级的p_id 和g_id 置空。
        Graduation graduation = new Graduation();
        graduation.setClassId(dl.getId());
        graduation.setEducationStageName(el.getName());
        graduation.setSchoolId(dl.getSchoolId());
        graduation.setGradeName(educationLevel.getName());
        userMapper.insertGraduation(graduation);//一班已经扔出去了
        educationLevelMapper.updateLevelpIdgIdIsnull(dl.getId(),null,null);
        //清空该毕业班级和老师的关联关系
        educationLevelMapper.deleteUserEducationLevelByLevelId(dl.getId());
    }


    /**
     * 这些是老师跟者班级走的逻辑 1升级2的逻辑
     * @param dl
     * @param list
     * @param count
     */
    public void headTeacher(EducationLevel dl,List<EducationLevel> list,int count){
        //创建一个班级，就是插入一条第三层层级，如果老师时跟着班级走的话，新生成的高一班是没有老师的
        Integer id=dl.getId();
        dl.setGradeDate(dl.getGradeDate()+1);
        dl.setId(null);
        educationLevelMapper.insertEducationLevel(dl);

        educationLevelMapper.updateLevelPid(id,list.get(count).getId());
    }

    /**
     * 这些是老师跟者班级走的逻辑 未毕业的逻辑
     * @param dl
     * @param list
     * @param count
     */
    public void centerTeacher(EducationLevel dl,List<EducationLevel> list,int count){
        educationLevelMapper.updateLevelPid(dl.getId(),list.get(count).getId());
    }

    /**
     * 这些是老师跟者班级走的逻辑 毕业的逻辑
     * @param dl
     * @param educationLevel
     * @param el
     */
    public void endTeacher(EducationLevel dl,EducationLevel educationLevel,EducationLevel el){
        //新表创建一条高三毕业数据和该高三或初三毕业班建立链接，并且把该高三毕业班级的p_id 和g_id 置空。
        Graduation graduation = new Graduation();
        graduation.setClassId(dl.getId());
        graduation.setEducationStageName(el.getName());
        graduation.setSchoolId(dl.getSchoolId());
        graduation.setGradeName(educationLevel.getName());
        graduation.setGradeDate(dl.getGradeDate());
        userMapper.insertGraduation(graduation);//一班已经剔除了
        educationLevelMapper.updateLevelpIdgIdIsnull(dl.getId(),null,null);//相当于已经剔除了
        //只清空该毕业班级（层级）和老师的关联关系（等于是把老师在该年级的权限剔除了），不删除任课老师表（毕业的所有学生数据其实也留存着，包括班级、任课老师、科目、是不是班主任等信息）

        //学生的在改版级的关联关系清除掉（等于是把学生在该年级的权限剔除了）

        //1、根据levelId 修改cefa_edu_user_education_level 表里的status 状态由0变为1
        educationLevelMapper.updateUserLevelByStatus(1,dl.getId());//老师和学生甚至包括管理者在该层的权限 都失效了，相当于逻辑删除
        //educationLevelMapper.deleteUserEducationLevelByLevelId(dl.getId());
    }



    /**
     * 学生自动升级
     */
    @Transactional("transactionManager")
    public void  studentCirculation2() {
      //  List<User> userList= userRoleMapper.getUserRoleByType(1);//一个学校只有一个admin角色用户,考虑到多个学校的情况
        List<Integer> schoolIdList=userOrganRoleMapper.getSchoolIdsBytRoleType(1);
        Map<Integer ,String> kindergarten=new HashMap<Integer,String>();//幼儿园
        kindergarten.put(1,"小班");
        kindergarten.put(2,"中班");
        kindergarten.put(3,"大班");
        kindergarten.put(4,"学前班");
        Map<Integer ,String> juniorSchool=new HashMap<Integer,String>();//小学
        juniorSchool.put(1,"一年级");
        juniorSchool.put(2,"二年级");
        juniorSchool.put(3,"三年级");
        juniorSchool.put(4,"四年级");
        juniorSchool.put(5,"五年级");
        juniorSchool.put(6,"六年级");
        Map<Integer ,String> middleSchool=new HashMap<Integer,String>();//初中
        middleSchool.put(1,"初一");
        middleSchool.put(2,"初二");
        middleSchool.put(3,"初三");
        Map<Integer ,String> seniorSchool=new HashMap<Integer,String>();//高中
        seniorSchool.put(1, "高一");
        seniorSchool.put(2, "高二");
        seniorSchool.put(3, "高三");
        Map<Integer ,Map<Integer ,String>> data= new HashMap<Integer ,Map<Integer ,String>>();

        List<Phase> list=null;
        String phaseName=null;
        Integer phaseSort=null;
        for (Integer schoolId:schoolIdList){
            //获取 指定学校的所有学习阶段
             list= phaseMapper.findPhaseListBySchoolId(schoolId);
            if(list!=null && list.size()>0){
                for(Phase phase:list){
                    phaseName=phase.getPhaseName();
                    phaseSort=phase.getSort();
                    if("高中".equals(phaseName)){
                        data.put(phaseSort,seniorSchool);
                    }
                    if("初中".equals(phaseName)){
                        data.put(phaseSort,middleSchool);
                    }
                    if("小学".equals(phaseName)){
                        data.put(phaseSort,juniorSchool);
                    }
                    if("幼儿园".equals(phaseName)){
                        data.put(phaseSort,kindergarten);
                    }

                }
            }
            /*
            data.put(3,kindergarten);
            data.put(5,juniorSchool);
            data.put(2,middleSchool);
            data.put(1,seniorSchool);
           */
            //1、查询出教育阶段list
            //2、for循环教育阶段 根据教育阶段id查询年级list （年级里有教育阶段类型）
            //3、如果是4表示高中，for循环年级list 修改他们的名称（修改规则，高一变高二 sout，高二变高三 sort+1，高三删除，循环外生成一个新的高一 级+1）
            //4、把之前sort=3的（高三）删掉的同时，要首先删掉他下面的所有班级数据，在删除权限关联表数据，在删除架构表信息，最后删除年级信息
            //5、生成新班级的时候，还有架构表信息需要添加
            Map<Integer ,String> gradesMap=null;
           for(Phase phase:list){
               //根据学校阶段 获取到对应的学校阶段集合
               if("高中".equals(phase.getPhaseName())){
                   gradesMap=seniorSchool;
               }
               if("初中".equals(phase.getPhaseName())){
                   gradesMap=middleSchool;
               }
               if("小学".equals(phase.getPhaseName())){
                   gradesMap=juniorSchool;
               }
               if("幼儿园".equals(phase.getPhaseName())){
                   gradesMap=kindergarten;
               }

               List<Grade> grades=gradeMapper.findGradeListByPhaseId(phase.getId());
                   for(Grade grade:grades){
                       //修改年级的名称和sort
                       if(grade.getSort()==1){//如果是小班，升级一个并且增加一个年级
                           firstData( grade,data.get(phase.getSort()), schoolId, phase);
                       }else if(grade.getSort()==phase.getGradeCount()){//如果是即将要毕业的年级
                           lastData(grade);
                       }else{
                           //gradeMapper.updateGradeById(grade.getId(),kindergarten.get(grade.getSort())+1);
                           gradeMapper.updateGradeById(grade.getId(),gradesMap.get(grade.getSort()+1));

                       }
                   }
           }
        }
    }


    public void firstData(Grade grade,Map<Integer,String> map,Integer schoolId,Phase phase){
        Grade grade1= gradeMapper.getGradeById2(grade.getId());
        //设置新增年级的级
        Calendar calendar=Calendar.getInstance();
        calendar.setTime(new Date());
        grade1.setGradeDate(calendar.get(Calendar.YEAR));
        gradeMapper.insertGrade(grade1);

        OrganRelation organRelation= new OrganRelation();
        organRelation.setSchoolId(schoolId);
        organRelation.setPhaseId(phase.getId());
        organRelation.setGradeId(grade1.getId());
        organRelation.setState(0);
        organRelationMapper.insertOrganRelation(organRelation);
        gradeMapper.updateGradeById(grade.getId(),map.get(grade.getSort()+1));//
    }
    public void lastData(Grade grade){
        //开始逻辑删除数据
        userOrganRoleMapper.deleteUserOrganRoleByGradeId(grade.getId());//删除权限关系表（年级这层的管理者要不要删除？？？）
        List<OrganRelation> organRelations=organRelationMapper.findOrganRelationByGradeId(grade.getId());
        StringBuilder sb = new StringBuilder();
        for(OrganRelation organRelation:organRelations){
            sb.append(organRelation.getClassId());
            sb.append(",");
        }
        if(sb.length()>0){
            sb=sb.deleteCharAt(sb.length()-1);
        }
        if(sb.length()>0){
            classMapper.deleteClassByIds(sb.toString());//删除班级
        }
        organRelationMapper.deleteOrganRelationByGradeId(grade.getId());//删除层级关联表
        //教育阶段数据改为已毕业状态1
        Integer endYear=TimeUtil.getCurrentYear();
        eduStageMapper.updateStageData(1,endYear,grade.getType(),grade.getId());

    }
}
